# -*- coding:utf8 -*-
'''
auth： Young
公众号：Python疯子 （Hold2Crazy）
'''
import wave
import contextlib
import numpy as np
import matplotlib.pyplot as plt
import math
import threading
import time
import copy
import os
from scipy.io import wavfile
from pydub import AudioSegment
from numpy import set_printoptions
from tencent_wav import speech_to_text

#!/usr/local/bin/env python3
import struct, sys

base = [str(x) for x in range(10)] + [chr(x) for x in range(ord('A'), ord('A') + 6)]

'''
    int(x [,base ])         将x转换为一个整数
    long(x [,base ])        将x转换为一个长整数
    float(x )               将x转换到一个浮点数
    complex(real [,imag ])  创建一个复数
    str(x )                 将对象 x 转换为字符串
    repr(x )                将对象 x 转换为表达式字符串
    eval(str )              用来计算在字符串中的有效Python表达式,并返回一个对象
    tuple(s )               将序列 s 转换为一个元组
    list(s )                将序列 s 转换为一个列表
    chr(x )                 将一个整数转换为一个字符
    unichr(x )              将一个整数转换为Unicode字符
    ord(x )                 将一个字符转换为它的整数值
    hex(x )                 将一个整数转换为一个十六进制字符串
    oct(x )                 将一个整数转换为一个八进制字符串
'''


def wav_infos(wav_path):
    '''
    获取音频信息

    :param wav_path: 音频路径
    :return: [1, 2, 8000, 51158, 'NONE', 'not compressed']
    对应关系：声道，采样宽度，帧速率，帧数，唯一标识，无损
    '''
    with wave.open(wav_path, "rb") as f:
        f = wave.open(wav_path)

        return list(f.getparams())

def read_wav(wav_path):
    '''
    读取音频文件内容:只能读取单声道的音频文件, 这个比较耗时

    :param wav_path: 音频路径
    :return:  音频内容
    '''
    with wave.open(wav_path, "rb") as f:
        # 读取格式信息
        # 一次性返回所有的WAV文件的格式信息，它返回的是一个组元(tuple)：声道数, 量化位数（byte单位）, 采
        # 样频率, 采样点数, 压缩类型, 压缩类型的描述。wave模块只支持非压缩的数据，因此可以忽略最后两个信息
        params = f.getparams()
        nchannels, sampwidth, framerate, nframes = params[:4]

        # 读取声音数据，传递一个参数指定需要读取的长度（以取样点为单位）
        str_data = f.readframes(nframes)

    return str_data

def get_wav_time(wav_path):
    '''
    获取音频文件是时长

    :param wav_path: 音频路径
    :return: 音频时长 (单位秒)
    '''
    with contextlib.closing(wave.open(wav_path, 'r')) as f:
        frames = f.getnframes()
    rate = f.getframerate()
    duration = frames / float(rate)
    return duration


def get_ms_part_wav(main_wav_path, start_time, end_time, part_wav_path):
    '''
    音频切片，获取部分音频 单位是毫秒级别

    :param main_wav_path: 原音频文件路径
    :param start_time:  截取的开始时间
    :param end_time:  截取的结束时间
    :param part_wav_path:  截取后的音频路径
    :return:
    '''
    start_time = int(start_time)
    end_time = int(end_time)

    sound = AudioSegment.from_mp3(main_wav_path)
    word = sound[start_time:end_time]

    word.export(part_wav_path, format="wav")


def get_second_part_wav(main_wav_path, start_time, end_time, part_wav_path):
    '''
    音频切片，获取部分音频 单位是秒级别

    :param main_wav_path: 原音频文件路径
    :param start_time:  截取的开始时间
    :param end_time:  截取的结束时间
    :param part_wav_path:  截取后的音频路径
    :return:
    '''
    start_time = int(start_time) * 1000
    end_time = int(end_time) * 1000

    sound = AudioSegment.from_mp3(main_wav_path)
    word = sound[start_time:end_time]

    word.export(part_wav_path, format="wav")

def get_minute_part_wav(main_wav_path, start_time, end_time, part_wav_path):
    '''
    音频切片，获取部分音频 分钟:秒数  时间样式："12:35"

    :param main_wav_path: 原音频文件路径
    :param start_time:  截取的开始时间
    :param end_time:  截取的结束时间
    :param part_wav_path:  截取后的音频路径
    :return:
    '''

    start_time = (int(start_time.split(':')[0])*60+int(start_time.split(':')[1]))*1000
    end_time = (int(end_time.split(':')[0])*60+int(end_time.split(':')[1]))*1000

    sound = AudioSegment.from_mp3(main_wav_path)
    word = sound[start_time:end_time]

    word.export(part_wav_path, format="wav")


def wav_to_pcm(wav_path, pcm_path):
    '''
    wav文件转为pcm文件

    :param wav_path:wav文件路径
    :param pcm_path:要存储的pcm文件路径
    :return: 返回结果
    '''
    f = open(wav_path, "rb")
    f.seek(0)
    f.read(44)

    data = np.fromfile(f, dtype=np.int16)
    data.tofile(pcm_path)

def pcm_to_wav(pcm_path, wav_path):
    '''
    pcm文件转为wav文件

    :param pcm_path: pcm文件路径
    :param wav_path: wav文件路径
    :return:
    '''
    f = open(pcm_path,'rb')
    str_data  = f.read()
    wave_out=wave.open(wav_path,'wb')
    wave_out.setnchannels(1)
    wave_out.setsampwidth(2)
    wave_out.setframerate(8000)
    wave_out.writeframes(str_data)

# 音频对应的波形图
def wav_waveform(wave_path):
    '''
    音频对应的波形图
    :param wave_path:  音频路径
    :return:
    '''
    file = wave.open(wave_path)
    # print('---------声音信息------------')
    # for item in enumerate(WAVE.getparams()):
    #     print(item)
    a = file.getparams().nframes  # 帧总数
    f = file.getparams().framerate  # 采样频率
    sample_time = 1 / f  # 采样点的时间间隔
    time = a / f  # 声音信号的长度
    sample_frequency, audio_sequence = wavfile.read(wave_path)
    # print(audio_sequence)  # 声音信号每一帧的“大小”
    x_seq = np.arange(0, time, sample_time)
    #set_printoptions(threshold=1000)
    print(audio_sequence)
    print(len(audio_sequence))

    plt.plot(x_seq, audio_sequence, 'blue')
    plt.xlabel("time (s)")
    plt.show()

def get_wave_info(wavfile):
    f = wave.open(wavfile)
    # 音频头 参数
    params = f.getparams()
    Channels = f.getnchannels()
    SampleRate = f.getframerate()
    bit_type = f.getsampwidth() * 8
    frames = f.getnframes()
    # Duration 也就是音频时长 = 采样点数/采样率
    Duration = wav_time = frames / float(SampleRate)  # 单位为s

    print("音频头参数：", params)
    print("通道数(Channels)：", Channels)
    print("采样率(SampleRate)：", SampleRate)
    print("比特(Precision)：", bit_type)
    print("采样点数(frames)：", frames)
    print("帧数或者时间(Duration)：", Duration)

def get_breakpoint_list(wav_path):

    duration = math.ceil(get_wav_time(wav_path))
    #print(wav_path)
    #print(duration)

    breakpoint_list = []

    if (duration <= 60):
        sub_start_time = 0
        sub_end_time = duration
        breakpoint_list.append([sub_start_time, sub_end_time])

    if (duration > 60):
        state = 0
        while (state < duration):
            if (state + 60 < duration):
                breakpoint_list.append([state, state + 60])
            else:
                breakpoint_list.append([state, duration])
            state += 60

    sub_file_num=math.ceil(duration/60)

    #print(sub_file_num)

    return breakpoint_list

def get_audio_text(wav_path):
    breakpoint_list=get_breakpoint_list(wav_path)
    #print(breakpoint_list)
    result=""
    for time_point in breakpoint_list:


        #print(time_point)
        file_split = os.path.splitext(wav_path)
        temp_file=file_split[0]+"tempt"+file_split[1]
        temp_path = os.path.join("../temp_file", temp_file)
        print("temppath:"+temp_path)
        start_time=time_point[0]
        end_time=time_point[1]
        get_second_part_wav(wav_path,start_time,end_time,temp_path)
        tempt_text=speech_to_text(temp_path)
        result+=tempt_text
        os.remove(temp_path)

    save_to_text(result, str(file_split[0]), "/Users/leslie/PycharmProjects/python_wav/txt")
    print(result)

    #get_second_part_wav()


def save_to_text(str,file_name,des_loction):
    text_name=file_name+".txt"
    save_path=os.path.join(des_loction,text_name)
    fh = open(save_path, 'w', encoding='utf-8')
    fh.write(str)
    fh.close()

def get_file_list(dir):

    file_list=[]

    for file in os.listdir(dir):

        file_split = os.path.splitext(file)
        file_list.append(file_split[0])

    return file_list

def process_file(process_dir,txt_list):
    try:
        os.mkdir(process_dir)
        os.mkdir(txt_dir)
    except:
        pass
    for file in os.listdir(process_dir):
        #print(file)
        try:
            #file_list = get_file_list(txt_list)
            #print("current processed file is %s"%file)
            file_split=os.path.splitext(file)
            #print((file_split[0]  in file_list ))
            if(file_split[1]==".wav" and (file_split[0] not in txt_list)) :

                txt_list.append(file_split[0])

                get_audio_text(file)

            else:

                print("exsited file")


        except:
            pass


if __name__ == '__main__':

    wav_path= "processed/1.wav"


    process_dir = "/Users/leslie/PycharmProjects/python_wav/processed"
    txt_dir = "/Users/leslie/PycharmProjects/python_wav/txt"

    txt_list=get_file_list(txt_dir)

    process_file(process_dir,txt_list)

    print("ending>>")








